package com.rerun.phone.intercepter;

import com.rerun.entity.MemberUser;
import com.rerun.service.IMemberUserService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.mvc.WebContentInterceptor;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.Map;

/**
 * The type App token validator.
 *
 * @author dax.
 * @version v1.0
 * @since 2017 /10/12 17:56
 */
public class AppTokenValidator extends WebContentInterceptor {
    private static final Logger log = LoggerFactory.getLogger(AppTokenValidator.class);
    private static final String TIMESTAMP_KEY = "timestamp";
    private static final String TOKEN_KEY = "token";
    private static final String MEMBER_KEY = "memberId";
    private static final int PATTERN = 50;
    private IMemberUserService iMemberUserService;

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws ServletException {
        if (!(handler instanceof HandlerMethod)) {
            log.info("handler is not  handlerMethod");
            return true;
        }
        HandlerMethod handlerMethod = (HandlerMethod) handler;
        RequestDecrypt requestDecrypt = handlerMethod.getMethodAnnotation(RequestDecrypt.class);
        if (requestDecrypt != null && requestDecrypt.value()) {
            Map<String, String[]> params = request.getParameterMap();
            if (params != null && params.containsKey(TOKEN_KEY) && params.containsKey(TIMESTAMP_KEY) && params.containsKey(MEMBER_KEY)) {
                String token = params.get(TOKEN_KEY)[0];
                String timestamp = params.get(TIMESTAMP_KEY)[0];
                String memberId = params.get(MEMBER_KEY)[0];
                if (!isInTime(timestamp, PATTERN)) {
                    String reason = "timestamp is overtime";
                    return setResponseForbidden(response, reason);
                }
                MemberUser member = iMemberUserService.selectById(memberId);
                if (member != null) {
                    String deviceId = "null";
                    if (!token.equals(MD5Encrypt.MD5Encoder(deviceId))) {
                        String reason = "token is invalid";
                        return setResponseForbidden(response, reason);
                    }
                }
            } else {
                return setResponseForbidden(response, "no required params");
            }
        }
        return super.preHandle(request, response, handler);
    }

    /**
     * @param timestamp 时间戳
     * @param pattern   超时设置
     * @return 是否超时
     */
    private boolean isInTime(String timestamp, int pattern) {
//        当前  1499678998500 1499679014207
        long now = System.currentTimeMillis();
//        请求
        long requestTimestamp = Long.parseLong(timestamp);
        double diff = (now - requestTimestamp) / 1000;
        return Math.abs(diff) <= pattern;
    }

    private boolean setResponseForbidden(HttpServletResponse response, String reason) {
        if (!"".equals(reason)) {
            log.info(reason);
        }
        response.setStatus(HttpServletResponse.SC_FORBIDDEN);
        return false;
    }

    /**
     * Gets member user service.
     *
     * @return the member user service
     */
    public IMemberUserService getiMemberUserService() {
        return iMemberUserService;
    }

    /**
     * Sets member user service.
     *
     * @param iMemberUserService the member user service
     */
    public void setiMemberUserService(IMemberUserService iMemberUserService) {
        this.iMemberUserService = iMemberUserService;
    }
}
